//
//  UIView+HoldFirstResponder.m
//
//  Created by KimmanYip on 2019/3/19.
//

#import "UIView+HoldFirstResponder.h"
#import <objc/runtime.h>

@implementation HoldFirstResponderHelper

- (instancetype)init
{
    self = [super init];
    if (self) {
        _holdingIdentifier = @"";
    }
    return self;
}

@end

@implementation UIView (HoldFirstResponder)

- (void)setTagIdentifier:(NSString *)tagIdentifier {
    objc_setAssociatedObject(self, @"HFRTagIdentifier", tagIdentifier, OBJC_ASSOCIATION_COPY_NONATOMIC);
}

- (NSString *)tagIdentifier {
    return objc_getAssociatedObject(self, @"HFRTagIdentifier");
}

- (void)pl_holdFirstResponderWithBlock:(void (^)(HoldFirstResponderHelper *helper))block {
    // 获取当前view的文本输入框
    NSMutableArray *array = [NSMutableArray arrayWithArray:[self getAllTextField]];
    
    // 获取当前第一响应者view的标识
    NSString *holdingIdentifier = @"";
    for (int i = 0;  i < array.count; i++) {
        UIView *view = array[i];
        if ([view isFirstResponder]) {
            holdingIdentifier = view.tagIdentifier;
            break ;
        }
    }
    
    // 刷新
    HoldFirstResponderHelper *helper = [HoldFirstResponderHelper new];
    if (block) {
        block(helper);
    }
    [self layoutIfNeeded];
    
    // 刷新后重新获取
    [array removeAllObjects];
    array = [NSMutableArray arrayWithArray:[self getAllTextField]];
    
    // 没有可用文本框，则结束 或 刷新前没有第一响应者
    if (array.count == 0 || holdingIdentifier.length == 0) {
        return;
    }
    
    UIView *holdingView;    // 需要保持第一响应者的view
    if (helper.holdingIdentifier.length > 0) {
        for (UIView *view in array) {
            if ([view.tagIdentifier isEqualToString:helper.holdingIdentifier]) {
                holdingView = view;
                break;
            }
        }
    }
    
    if (holdingView) {
        [holdingView becomeFirstResponder];
    }
}

#pragma mark - 获取当前view的所有的可输入文本框
// 获得当前控制器的所有的文本框
- (NSArray *)getAllTextField {
    // 获得所有的文本框，默认按照位置排序
    NSArray *textArray = [self deepResponderViews:self];
    
    return textArray;
}

// 通过递归，来获得控件中的所有的textField
- (NSArray*)deepResponderViews:(UIView *)superView {
    NSMutableArray *textFields = [[NSMutableArray alloc] init];
    for (UIView *textField in superView.subviews) {
        if ([self canBecomeFirstResponder:textField]) {
            [textFields addObject:textField];
        }
        if (textField.subviews.count && [textField isUserInteractionEnabled] && ![textField isHidden] && [textField alpha]!=0.0) {
            [textFields addObjectsFromArray:[self deepResponderViews:textField]];
        }
    }
    // 按照位置从上到下，（从左到右进行排序）
    __weak __typeof(self) weakself = self;
    return [textFields sortedArrayUsingComparator:^NSComparisonResult(UIView *view1, UIView *view2) {
        CGRect frame1 = [view1 convertRect:view1.bounds toView:weakself];
        CGRect frame2 = [view2 convertRect:view2.bounds toView:weakself];
        
        CGFloat x1 = CGRectGetMinX(frame1);
        CGFloat y1 = CGRectGetMinY(frame1);
        CGFloat x2 = CGRectGetMinX(frame2);
        CGFloat y2 = CGRectGetMinY(frame2);
        
        if (y1 < y2) {
            return NSOrderedAscending;
        } else if (y1 > y2) {
            return NSOrderedDescending;
        }
        //Else both y are same so checking for x positions
        else if (x1 < x2) {
            return NSOrderedAscending;
        } else if (x1 > x2) {
            return NSOrderedDescending;
        } else {
            return NSOrderedSame;
        }
    }];
    
    return textFields;
}

// 是否是可以响应的文本框
-(BOOL)canBecomeFirstResponder:(UIView *)view {
    BOOL canBecomeFirstResponder = NO;
    if ([view isKindOfClass:[UITextField class]]) {
        canBecomeFirstResponder = [(UITextField*)view isEnabled];
    } else if ([view isKindOfClass:[UITextView class]]) {
        canBecomeFirstResponder = [(UITextView*)view isEditable];
    }
    if (canBecomeFirstResponder == YES) {
        canBecomeFirstResponder = ([view isUserInteractionEnabled] && ![view isHidden] && [view alpha]!=0.0 && ![self isAlertViewTextField:view]  && ![self isSearchBarTextField:view]);
    }
    return canBecomeFirstResponder;
}

// 是否是alertView中的文本框
-(BOOL)isAlertViewTextField:(UIView *)view {
    UIResponder *alertViewController = [self viewController];
    BOOL isAlertViewTextField = NO;
    while (alertViewController && isAlertViewTextField == NO) {
        if ([alertViewController isKindOfClass:[UIAlertController class]]) {
            isAlertViewTextField = YES;
            break;
        }
        alertViewController = [alertViewController nextResponder];
    }
    return isAlertViewTextField;
}

// 是否是搜索框
-(BOOL)isSearchBarTextField:(UIView *)view {
    UIResponder *searchBar = [self nextResponder];
    BOOL isSearchBarTextField = NO;
    while (isSearchBarTextField == NO) {
        if ([searchBar isKindOfClass:[UISearchBar class]]) {
            isSearchBarTextField = YES;
            break;
        } else if ([searchBar isKindOfClass:[UIViewController class]]) {
            break;
        }
        searchBar = [searchBar nextResponder];
    }
    return isSearchBarTextField;
}

- (UIViewController *)viewController {
    UIResponder *next = [self nextResponder];
    do {
        if ([next isKindOfClass:[UIViewController class]]) {
            return (UIViewController *)next;
        }
        next = [next nextResponder];
    } while (next != nil);
    return nil;
}

@end
